%{
        #include<stdlib.h>


/*definições das constantes manifestas
	LT,LE,EQ,NE,GT,GE
	IF,THEN,ELSE,ID,NUMERO,RELOP */
	#define LT 1
	#define LE 2
	#define EQ 3
	#define NE 4
	#define GT 5
	#define GE 6
	#define IF 7	
	#define THEN 8
	#define ELSE 9
	#define ID 10
	#define NUMERO 11
	#define RELOP 12

	#define VAR 13
	#define CONST 14
	#define TYPE 15
	#define PROGRAM 16
	#define INICIO 17
	#define FIM 18
	#define FOR 19
	#define WHILE 20
	#define DO 21
	#define TO 22
	#define DOWNTO 23
	#define STEP 24
	#define REPEAT 25
	#define UNTIL 26
	#define CASE 27
	#define FUNCTION 28
	#define PROCEDURE 29
	#define ASPECT 30
	#define BEFORE 31
	#define AFTER 32
	#define WRITELN 33
	#define READLN 34
	#define RECORD 35
	#define ARRAY 36
	#define RANGE 37
	#define TRUE 38
	#define FALSE 39
	#define BOOLEAN 40
	#define REAL_TYPE 41
	#define REAL 42
	#define INTEGER 43
	#define STRING_TYPE 44
	#define CHAR_TYPE 45
	#define STRING 46
	#define CHAR 47

	#define OF 48
	#define POINTER 49
	#define OP_ARITMETICO 50
	#define ATRIBUICAO 51
	#define DOISPONTOS 52
	#define PONTO 53
	#define VIRGULA 54
	#define PONTOEVIRGULA 55
	#define ABRECOL 56
	#define FECHACOL 57
	#define ABREPAR 58
	#define FECHAPAR 59

	#define MAIS 60
	#define MULT 61
	#define DIV 62
	#define MOD 63
	#define MENOS 64 

	#define NAO 65
	#define OP_LOGICO 66
	#define EE 67
	#define OU 68

        

	int yylval = 0;

       typedef struct tokenElement
        {
            int token;
            int lexem;
        }tE;

        static int tamTabela = 0;
        static int lastPos = 0;
        tE * tabelaSimbolos;
%}

/* definições regulares */
delim	[ \t\n]
ws	{delim}+
letra	[A-Za-z]
digito  [0-9]
espechar ("."|","|";"|"("|"*"|"!"|"~"|"@"|"#"|"$"|"%"|"^"|"&"|"*"|"("|")"|"-"|"_"|"+"|"="|"`"|"{"|"}"|"["|"]"|"|"|":"|"<"|">"|"?"|"/")
id	{letra}({letra}|{digito})*
float	[\-]?{digito}+(\.{digito}+)(E[+\-]?{digito}+)?
numero  [\-]?{digito}*
string  	\"({delim}|{letra}|{digito}|{espechar})*\"
char		\'({delim}|{letra}|{digito}|{espechar})\'

%Start comment0 comment1

%%

<INITIAL>"/*"			{ BEGIN(comment0); }
<comment0>\*			{ BEGIN(comment1); }
<comment0>.			{;}
<comment1>\*			{;}
<comment1>\/			{ BEGIN(INITIAL); }
<comment1>.			{ BEGIN(comment0); }

<INITIAL>{ws}		{/*nenhuma ação e nenhum valor retornado */}
<INITIAL>var		{printf(" Var ");return (VAR);}
<INITIAL>const		{printf(" Const ");return (CONST);}
<INITIAL>program		{printf(" Program ");return (PROGRAM);}
<INITIAL>repeat		{printf(" repeat ");return (REPEAT);}
<INITIAL>until		{printf(" until ");return (UNTIL);}
<INITIAL>type		{printf(" type ");return (TYPE);}
<INITIAL>if		{printf(" if ");return (IF);}
<INITIAL>of		{printf(" of ");return (OF);}
<INITIAL>then		{printf(" then ");return (THEN);}
<INITIAL>else		{printf(" else ");return (ELSE);}
<INITIAL>for		{printf(" for ");return (FOR)	;}
<INITIAL>while		{printf(" while ");return (WHILE);}		
<INITIAL>do		{printf(" do ");return (DO);}
<INITIAL>begin		{printf(" INICIO ");return (INICIO);}
<INITIAL>end		{printf(" FIM ");return (FIM);}
<INITIAL>to		{printf(" TO ");return (TO);}
<INITIAL>step		{printf(" step ");return (STEP);}
<INITIAL>downto		{printf(" downto ");return (DOWNTO);}
<INITIAL>procedure	{printf(" procedure ");return (PROCEDURE);}
<INITIAL>function	{printf(" function ");return (FUNCTION);}
<INITIAL>record		{printf(" record ");return (RECORD);}
<INITIAL>array		{printf(" array ");return (ARRAY);}
<INITIAL>writeln		{printf(" writeln ");return (WRITELN);}
<INITIAL>readln		{printf(" readln ");return (READLN);}
<INITIAL>aspect		{printf(" aspect ");return (ASPECT);}
<INITIAL>before		{printf(" before ");return (BEFORE);}
<INITIAL>after		{printf(" after ");return (AFTER);}
<INITIAL>true		{printf(" true ");return (TRUE);}
<INITIAL>false		{printf(" false ");return (FALSE);}
<INITIAL>case		{printf(" case ");return (CASE);}
<INITIAL>boolean		{printf(" boolean ");return (BOOLEAN);}
<INITIAL>string		{printf(" string ");return (STRING_TYPE);}
<INITIAL>char		{printf(" char ");return (CHAR_TYPE);}
<INITIAL>real		{printf(" real ");return (REAL_TYPE);}
<INITIAL>integer		{printf(" integer ");return (INTEGER);}
<INITIAL>"^"		{printf(" pointer ");return (POINTER);}
<INITIAL>".."		{printf(" range ");return (RANGE);}
<INITIAL>":"		{printf(" dois-pontos ");return (DOISPONTOS);}
<INITIAL>"+"		{printf(" mais "); return (MAIS);}
<INITIAL>"*"		{printf(" OP_ARITMETICO ");yylval = MULT; return (OP_ARITMETICO);}
<INITIAL>"/"		{printf(" OP_ARITMETICO ");yylval = DIV; return (OP_ARITMETICO);}
<INITIAL>"%"		{printf(" OP_ARITMETICO ");yylval = MOD; return (OP_ARITMETICO);}
<INITIAL>"-"		{printf(" OP_ARITMETICO ");yylval = MENOS; return (OP_ARITMETICO);}
<INITIAL>"!"		{printf(" not ") ;return (NAO);}
<INITIAL>":="		{printf(" atribuicao ");return (ATRIBUICAO);}
<INITIAL>";"		{printf(" pontoevirgula ");return (PONTOEVIRGULA);}		
<INITIAL>"&&"		{printf(" OP_LOGICO ");yylval = EE; return (OP_LOGICO);}		
<INITIAL>"||"		{printf(" OP_LOGICO ");yylval = OU; return (OP_LOGICO);}		
<INITIAL>"["		{printf(" AbreCol ");return (ABRECOL);}
<INITIAL>"]"		{printf(" FechaCol ");return (FECHACOL);}
<INITIAL>"("		{printf(" AbrePar ");return (ABREPAR);}
<INITIAL>")"		{printf(" FechaPar ");return (FECHAPAR);}
<INITIAL>"."		{printf(" ponto ");return (PONTO);}
<INITIAL>","		{printf(" virgula ");return (VIRGULA);}			
<INITIAL>{numero}	{printf(" numero ");return (NUMERO);}
<INITIAL>{id}		{printf(" id ");yylval = instalar_id();return (ID);}
<INITIAL>{float} 	{printf(" float ");yylval = instalar_num(); return (REAL);}
<INITIAL>"<"		{printf(" RELOP ");yylval = LT; return (RELOP);}
<INITIAL>"<="		{printf(" RELOP ");yylval = LE; return (RELOP);}
<INITIAL>"=="		{printf(" RELOP ");yylval = EQ; return (RELOP);}
<INITIAL>"!="		{printf(" RELOP ");yylval = NE; return (RELOP);}
<INITIAL>">"		{printf(" RELOP ");yylval = GT; return (RELOP);}
<INITIAL>">="		{printf(" RELOP ");yylval = GE; return (RELOP);}

<INITIAL>{string}	{printf(" string\n");return (STRING);}
<INITIAL>{char}		{printf(" char\n");return (CHAR);}
.			{;}
	
%%

yywrap(){
	return 1;
}


int instalar_id(){
	/* procedimento para instalar o lexema, cujo primeiro caractere é apontado por yytext e cujo comprimento é yyleng, na tabela de símbolos e retornar um apontador para o mesmo */
	return 2;
        if(tamTabela == 0)
        {
            tabelaSimbolos = (tE*)malloc(sizeof(tE)*15);
        }

}


int instalar_num(){
	/* procedimento similar para instalar um lexema que seja um número */
	return 1;
}

